package com.liuqi.aiagent.service.impl;

import com.liuqi.aiagent.ai.tool.ToolType;
import com.liuqi.aiagent.mapper.AgentEventMapper;
import com.liuqi.aiagent.mapper.AgentMapper;
import com.liuqi.aiagent.mapper.AgentToolBindingMapper;
import com.liuqi.aiagent.service.AgentChatManager;
import com.liuqi.aiagent.service.AgentService;
import com.liuqi.aiagent.transfer.ApiResult;
import com.liuqi.aiagent.transfer.dto.AgentEditDto;
import com.liuqi.aiagent.transfer.dto.AgentPublishUpdateDto;
import com.liuqi.aiagent.transfer.dto.AgentSaveDto;
import com.liuqi.aiagent.transfer.entity.Agent;
import com.liuqi.aiagent.transfer.entity.AgentToolBinding;
import com.liuqi.aiagent.transfer.mapstruct.AgentMapStruct;
import com.liuqi.aiagent.transfer.model.Result;
import com.liuqi.aiagent.transfer.model.ResultList;
import com.liuqi.aiagent.transfer.vo.AgentInfoVo;
import com.liuqi.aiagent.transfer.vo.AgentVo;
import java.util.ArrayList;
import java.util.List;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

/**
 * @author liuqi
 * @date 2025/7/16
 **/
@Service
@Slf4j
public class AgentServiceImpl implements AgentService {

    private final AgentMapper agentMapper;

    private final AgentToolBindingMapper agentToolBindingMapper;

    private final AgentEventMapper agentEventMapper;

    @Autowired
    @Lazy
    private AgentChatManager agentChatManager;

    @Autowired
    public AgentServiceImpl(AgentMapper agentMapper,
                            AgentToolBindingMapper agentToolBindingMapper,
                            AgentEventMapper agentEventMapper) {
        this.agentMapper = agentMapper;
        this.agentToolBindingMapper = agentToolBindingMapper;
        this.agentEventMapper = agentEventMapper;
    }

    @Override
    public Result save(AgentSaveDto agentSaveDto) {
        if (agentMapper.exitsByName(agentSaveDto.getName()) != null) {
            return ApiResult.fail("名称已存在");
        }
        log.info("添加 Agent: 名称[{}]", agentSaveDto.getName());
        agentMapper.save(AgentMapStruct.INSTANCE.from(agentSaveDto));
        return ApiResult.success();
    }

    @Override
    public Result edit(AgentEditDto agentEditDto) {
        log.info("编辑 Agent: Id[{}]", agentEditDto.getId());
        agentMapper.edit(AgentMapStruct.INSTANCE.from(agentEditDto));
        return ApiResult.success();
    }

    @Override
    public Result delete(Integer id) {
        log.warn("删除Agent, Agent id[{}]", id);
        agentMapper.delete(id);
        return ApiResult.success();
    }

    @Override
    public ResultList<AgentVo> findAll() {
        List<Agent> agents = agentMapper.findAll();
        List<AgentVo> agentVos = AgentMapStruct.INSTANCE.toVos(agents);
        return ApiResult.success(agentVos, agentVos.size());
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Result publishUpdate(AgentPublishUpdateDto updateDto) {
        Agent agent = agentMapper.findByIdOfBrief(updateDto.getAgentId());
        if (agent == null) {
            return ApiResult.fail("Agent 不存在");
        }

        log.info("Agent 发布更新. agent name = {}", agent.getName());

        // 更新 agent
        agentMapper.edit(AgentMapStruct.INSTANCE.from(updateDto));

        // 清理Agent和工具的关联
        agentToolBindingMapper.deleteByAgentId(updateDto.getAgentId());

        Integer[] webhookIds = updateDto.getWebhookIds();
        if (webhookIds == null || webhookIds.length == 0) {
            log.info("Agent 发布更新. agent name = {}, webhookIds 为空", agent.getName());
        } else {
            List<AgentToolBinding> agentToolBindings = new ArrayList<>(webhookIds.length);
            for (Integer id : webhookIds) {
                agentToolBindings.add(new AgentToolBinding(updateDto.getAgentId(), id, ToolType.WEB_HOOK.type()));
            }

            // 添加Agent和工具的关联
            agentToolBindingMapper.saveBatch(agentToolBindings);
        }

        log.info("Agent 发布更新. agent name = {}, 发布成功", agent.getName());

        // 更新agent的事件为处理状态
        agentEventMapper.updateStatus(updateDto.getAgentId());

        // 移除 agent 的缓存
        agentChatManager.removeCache(agent.getName());

        return ApiResult.success();
    }

    @Override
    public Result<AgentInfoVo> info(Integer agentId) {
        // 查询 Agent Info
        Agent agent = agentMapper.findById(agentId);

        AgentInfoVo agentInfoVo = buildInfo(agent);

        return ApiResult.success(agentInfoVo);
    }

    @Override
    public AgentInfoVo info(String agentName) {
        Agent agent = agentMapper.findByName(agentName);
        return buildInfo(agent);
    }

    @Override
    public ResultList<String> findEventMessages(Integer agentId) {
        // 查询eventMessage
        List<String> eventMessages = agentEventMapper.findMessages(agentId);
        return ApiResult.success(eventMessages, eventMessages.size());
    }

    private AgentInfoVo buildInfo(Agent agent) {
        // 查询Agent 关联的webhook工具
        List<String> webhookIds = agentToolBindingMapper.findWebhookIds(agent.getId());

        AgentInfoVo agentInfoVo = AgentMapStruct.INSTANCE.toInfoVo(agent);
        agentInfoVo.setWebhookIds(webhookIds);

        return agentInfoVo;
    }

}
